import { Vector3, Spherical } from "../three.module.js";

//球体
export default class Sphere {
    constructor(r = 0.1, widthSegments = 3, heightSegments = 2) {
        this.r = r;
        this.widthSegments = widthSegments;
        this.heightSegments = heightSegments;

        this.normals = [];//顶点法向
        this.vertices = [];//顶点信息
        this.elements = [];//默认的Elements
        this.elementsOfLine = [];//默认的线框Elements
        this.count = 0;

        this._init();
    }

    _init() {
        const { widthSegments, heightSegments, normals, vertices, r } = this;
        this.count = widthSegments * (heightSegments - 1) + 2;

        //加入顶点
        vertices.push(0, r, 0);
        normals.push(0, 1, 0);

        const perW = 360 / widthSegments;
        const perH = 180 / heightSegments;
        const spherical = new Spherical().setFromVector3(
            new Vector3(0, r, 0).sub(new Vector3(0, 0, 0))
        );

        for (let i = 0; i < heightSegments - 1; i++) {
            for (let j = 0; j < widthSegments; j++) {
                spherical.theta = j * perW * Math.PI / 180;
                spherical.phi = (i + 1) * perH * Math.PI / 180;
                const rotateOffset = new Vector3().setFromSpherical(spherical);
                vertices.push(...rotateOffset);
                normals.push(...rotateOffset.normalize())
            }
        }

        //加入末点
        vertices.push(0, -r, 0);
        normals.push(0, -1, 0);

        this._createElementsOfFace();
    }

    _createElementsOfFace() {
        const { vertices, elements, widthSegments, heightSegments } = this;
        for (let i = 0; i < heightSegments; i++) {
            for (let j = 0; j < widthSegments; j++) {

                if (i == 0) {
                    //第一行
                    let t = 0;
                    let l = j + 1;
                    let r = j + 2;
                    if (r > widthSegments) {
                        r = 1;
                    }
                    elements.push(t, l, r);
                } else if (i == heightSegments - 1) {
                    //最后一行
                    let cur = (i - 1) * widthSegments;
                    let maxcur = i * widthSegments;
                    let l = cur + j + 1;
                    let r = cur + j + 2;
                    if (r > maxcur) {
                        r = cur + 1;
                    }
                    let b = vertices.length / 3 - 1;
                    elements.push(l, b, r);
                } else {
                    //中间行
                    let tl = 1 + (i - 1) * widthSegments + j;
                    let tr = tl + 1;
                    let bl = 1 + i * widthSegments + j;
                    let br = bl + 1;
                    if (j == widthSegments - 1) {
                        tr -= widthSegments;
                        br -= widthSegments;
                    }
                    elements.push(tl, bl, br, tl, br, tr);
                }
            }
        }
    }

    _createElementsOfLine() {
        const { vertices, elementsOfLine, widthSegments, heightSegments } = this;
        for (let i = 0; i < heightSegments; i++) {
            for (let j = 0; j < widthSegments; j++) {
                if (i == 0) {
                    //第一行
                    let t = 0;
                    let l = j + 1;
                    let r = j + 2;
                    if (r > widthSegments) {
                        r = 1;
                    }
                    elementsOfLine.push(t, l, t, r, l, r);
                } else if (i == heightSegments - 1) {
                    //最后一行
                    let cur = (i - 1) * widthSegments;
                    let maxcur = i * widthSegments;
                    let l = cur + j + 1;
                    let r = cur + j + 2;
                    if (r > maxcur) {
                        r = cur + 1;
                    }
                    let b = vertices.length / 3 - 1;
                    elementsOfLine.push(l, b, r, b, l, r);
                } else {
                    //中间行
                    let tl = 1 + (i - 1) * widthSegments + j;
                    let tr = tl + 1;
                    let bl = 1 + i * widthSegments + j;
                    let br = bl + 1;
                    if (j == widthSegments - 1) {
                        tr -= widthSegments;
                        br -= widthSegments;
                    }
                    elementsOfLine.push(
                        tl, bl, bl, br, br, tl,
                        tl, br, br, tr, tr, tl
                    );

                }
            }
        }
    }

    //获取线框的Elemenets
    getElementsOfLine() {
        const { elementsOfLine } = this;
        if (elementsOfLine.length == 0) {
            this._createElementsOfLine();
        }
        return elementsOfLine;
    }

}